/**
 * @file bl6552.c
 * @brief 7通道三相电能监测及分析专用芯片驱动
 * @author wangh (wanghuan3037@fiberhome.com)
 * @version 1.0
 * @date 2021-03-01
 * @copyright Copyright (c) 2021  烽火通信
 */ 
#include "bl6552.h"
#include <math.h>

#if DRV_BL6552_EN
#include "project_board.h"

#undef LOG_LEVEL_
#define LOG_LEVEL_ 	LOG_LVL_DEBUG
#include "bsp_log.h"

#define BL_READ_TIMEOUT         100     ///< 读取超时
#define BL_READ_TRYTIMES        3       ///< 重试次数
#define BL_RESUME_TRYTIMES      10

static int8_t Bl6552_Config(Bl6552_t *obj);

/**
 * @brief 计算校验和 \n
 * （Addr+Data_L+Data_M+Data_H）&0xFF 取反
 * @param  buff        数据指针
 * @param  size        数据长度
 * @return uint8_t 校验和
 */
static uint8_t Bl_CaclCheckSum( uint8_t *buff, uint8_t size )
{
    uint16_t checksum = 0;
    for( uint8_t i=0; i<size; i++ )
        checksum = checksum + buff[i];
    return ~(uint8_t)(checksum&0xFF);
}


/**
 * @brief Bl6552读寄存器(无锁版，中间函数)
 * @param[in]  obj      Bl6552对象
 * @param[in]  reg      寄存器地址
 * @param[in]  buffer   读取数据指针
 * @param[in]  timeout  读取超时时间（ms）
 * @param[in]  trytimes 出错重试次数
 * @return int8_t 
 * - @b Sucess : BSP_SUCCESS \n
 * - @b Fail : BSP_ERROR - 超时或校验出错
 */
static int8_t Bl6552_ReadReg_Nolock( Bl6552_t *obj, uint8_t reg, uint8_t *buffer, uint32_t timeout, uint8_t trytimes )
{
    uint8_t buff[6];

    memset(buff, 0, 6);
    buff[0] = 0x35;
    buff[1] = reg;

    do{
        vTaskDelay(1);
        UartSend( obj->UartId, buff, 2 );
        if( UartRecv( obj->UartId, &buff[2], 4, portTICK_RATE_MS*timeout ) == 4 )
        {
            if( buff[5] == Bl_CaclCheckSum( &buff[1], 4 ) ) /* 比对校验和 */
            {
                memcpy(buffer, &buff[2], 3);
                obj->resume_times = 0;
                return BSP_SUCCESS;
            }
            else
                log_d( "Bl_CaclCheckSum error!\r\n" );
        }
        else
        {
            log_d( "Bl6552_recv timeout!\r\n" );
        }
    } while (trytimes--);

    log_e( "Bl6552_ReadReg timeout\r\n" );
    obj->resume_times++;
    if (obj->resume_times > BL_RESUME_TRYTIMES)
    {
        obj->resume_times = 0;
        UartReset( obj->UartId );   /* 复位串口回复 */
    }

    return BSP_ERROR;
}

/**
 * @brief Bl6552读寄存器
 * @param[in]  obj      Bl6552对象
 * @param[in]  reg      寄存器地址
 * @param[in]  buffer   读取数据指针
 * @param[in]  timeout  读取超时时间（ms）
 * @param[in]  trytimes 出错重试次数
 * @return int8_t 
 * - @b Sucess : BSP_SUCCESS \n
 * - @b Fail : BSP_ERROR - 超时或校验出错
 */
static int8_t Bl6552_ReadReg( Bl6552_t *obj, uint8_t reg, uint8_t *buffer, uint32_t timeout, uint8_t trytimes )
{
    xSemaphoreTake(obj->WR_lock, portMAX_DELAY);
    int8_t ret = Bl6552_ReadReg_Nolock( obj, reg, buffer, timeout, trytimes );
    xSemaphoreGive(obj->WR_lock);
    return ret;
}

/**
 * @brief Bl6552写寄存器（不校验、不加锁，中间函数）
 * @param[in]  obj      Bl6552对象
 * @param[in]  reg      寄存器地址
 * @param[in]  data     数据（24位）
 */
static void Bl6552_WriteReg_Nocheck( Bl6552_t *obj, uint8_t reg, uint32_t data )
{
    uint8_t buff[6];

    buff[0] = 0xCA;
    buff[1] = reg;
    buff[2] = (uint8_t)(data&0xFF);
    buff[3] = (uint8_t)((data>>8)&0xFF);
    buff[4] = (uint8_t)((data>>16)&0xFF);
    buff[5] = Bl_CaclCheckSum( &buff[1], 4 );   /* 校验和 */

    UartSend( obj->UartId, buff, 6 );
}

/**
 * @brief Bl6552写寄存器（仅支持用户操作寄存器）
 * @param[in]  obj      Bl6552对象
 * @param[in]  reg      寄存器地址
 * @param[in]  data     数据（24位）
 * @param[in]  isReadCheck 是否读取验证（false：不验证，true：验证）
 * @return int8_t 
 * - @b Sucess : BSP_SUCCESS \n
 * - @b Fail : BSP_ERROR - 超时或校验出错
 */
static int8_t Bl6552_WriteReg( Bl6552_t *obj, uint8_t reg, uint32_t data, bool isReadCheck )
{
    int8_t ret = BSP_ERROR;
	uint8_t buff[6];
    uint8_t trytimes = BL_READ_TRYTIMES;

    xSemaphoreTake(obj->WR_lock, portMAX_DELAY);
    if (!isReadCheck)
    {
        Bl6552_WriteReg_Nocheck( obj, reg, data );
        ret = BSP_SUCCESS;
        goto end;
    }

    /* 读取验证 */
    do{
        Bl6552_WriteReg_Nocheck( obj, reg, data );

        memset(buff, 0, 6);
        ret = Bl6552_ReadReg_Nolock( obj, reg, buff, BL_READ_TIMEOUT, 1 );
        if (ret == BSP_SUCCESS)
        {
            if( data == (uint32_t)(((buff[2]<<16) + (buff[1]<<8) + buff[0])&0x00FFFFFF) )
            {
                ret = BSP_SUCCESS;
                obj->resume_times = 0;
                goto end;
            }
            else
            {
                log_e( "Bl6552_WriteReg check error %08X  %08X\r\n", data, (uint32_t)(((buff[2]<<16) + (buff[1]<<8) + buff[0])&0x00FFFFFF) );
                ret = BSP_ERROR_CHECK;
            }
        }
    } while (trytimes--);

    obj->resume_times++;
    if (obj->resume_times > BL_RESUME_TRYTIMES)
    {
        obj->resume_times = 0;
        UartReset( obj->UartId );   /* 复位串口回复 */
    }

end:
    xSemaphoreGive(obj->WR_lock);
    return ret;
}

/**
 * @brief 读无符号寄存器
 * @param[in]  obj      Bl6552对象
 * @param[in]  reg      寄存器地址
 * @param[out] value    寄存器值
 * @return int8_t 
 * - @b Sucess : BSP_SUCCESS \n
 * - @b Fail : @ref Bl6552_ReadReg
 */
static int8_t Bl6552_ReadRegUint( Bl6552_t *obj, uint8_t reg, uint32_t *value )
{
    uint8_t buff[3];
    memset(buff, 0, 3);

    int8_t ret = Bl6552_ReadReg( obj, reg, buff, BL_READ_TIMEOUT, BL_READ_TRYTIMES );
    if(ret != BSP_SUCCESS)
    {
        log_e( "Bl6552_ReadReg error(%d)\r\n", ret );
        return ret;
    }
    log_v("Bl6552_ReadReg %02X %02X %02X\r\n", buff[0], buff[1], buff[2]);

    *value = (uint32_t)(((buff[2]<<16) + (buff[1]<<8) + buff[0])&0x00FFFFFF);

    return BSP_SUCCESS;
}

/**
 * @brief 读有符号寄存器
 * @param[in]  obj      Bl6552对象
 * @param[in]  reg      寄存器地址
 * @param[out] value    寄存器值
 * @return int8_t 
 * - @b Sucess : BSP_SUCCESS \n
 * - @b Fail : @ref Bl6552_ReadReg
 */
static int8_t Bl6552_ReadRegInt( Bl6552_t *obj, uint8_t reg, int32_t *value )
{
    uint32_t utemp;

    int8_t ret = Bl6552_ReadRegUint( obj, reg, &utemp );
    if (ret != BSP_SUCCESS)
        return ret;

    int32_t itemp = (int32_t)utemp;
    if( ( itemp&0x800000 ) == 0x800000 )
        itemp |= 0xff000000; /* 高位补1 */

    *value = itemp;

    return BSP_SUCCESS;
}

/**
 * @brief 电量统计超时处理函数
 */
static void blTimer_timeout_ind(TimerHandle_t xTimer)
{
    Bl6552_t *obj = (Bl6552_t * )pvTimerGetTimerID(xTimer);

    uint32_t utempA = 0;
    uint32_t utempB = 0;
    uint32_t utempC = 0;
    uint32_t utemp = 0;

    Bl6552_ReadRegUint( obj, Addr_ADC_PD, &utemp );
    log_v("Addr_ADC_PD = %08X\r\n", utemp);
    if (utemp != 0x0C3)
    {
        Bl6552_Config(obj);
        log_e( "Bl6552 reconfig...\r\n" );
        return;
    }

    if (BSP_SUCCESS != Bl6552_ReadRegUint( obj, Addr_CF_A_CNT, &utempA ))
        return;

    if (BSP_SUCCESS != Bl6552_ReadRegUint( obj, Addr_CF_B_CNT, &utempB ))
        return;

    if (BSP_SUCCESS != Bl6552_ReadRegUint( obj, Addr_CF_C_CNT, &utempC ))
        return;

    if (BSP_SUCCESS != Bl6552_ReadRegUint( obj, Addr_CF_CNT, &utemp ))
        return;

#if BL6552_CF_CLR_SEL   /* CF自动清零 */
#if (BL6552_ENERGY_USE_FLOAT)   /* 使用浮点运算 */
    xSemaphoreTake(obj->Energy_lock, portMAX_DELAY);
    obj->Energy.Energy_A.value = obj->Energy.Energy_A.value + (float)(utempA/obj->Energy_K);
    obj->Energy.Energy_B.value = obj->Energy.Energy_B.value + (float)(utempB/obj->Energy_K);
    obj->Energy.Energy_C.value = obj->Energy.Energy_C.value + (float)(utempC/obj->Energy_K);
    obj->Energy.Energy.value = obj->Energy.Energy.value + (float)(utemp*4/obj->Energy_K);
    xSemaphoreGive(obj->Energy_lock);

#else   /* 使用整形运算 */
    utempA = utempA*1000 + obj->EnergyMid.EnergyMid_A;
    utempB = utempB*1000 + obj->EnergyMid.EnergyMid_B;
    utempC = utempC*1000 + obj->EnergyMid.EnergyMid_C;
    utemp = utemp*1000 + obj->EnergyMid.EnergyMid;

    obj->EnergyMid.EnergyMid_A = utempA % obj->Energy_K;
    obj->EnergyMid.EnergyMid_B = utempB % obj->Energy_K;
    obj->EnergyMid.EnergyMid_C = utempC % obj->Energy_K;
    obj->EnergyMid.EnergyMid = (utemp*4) % obj->Energy_K;

    xSemaphoreTake(obj->Energy_lock, portMAX_DELAY);
    obj->Energy.Energy_A.value = obj->Energy.Energy_A.value + utempA/obj->Energy_K;
    obj->Energy.Energy_B.value = obj->Energy.Energy_B.value + utempB/obj->Energy_K;
    obj->Energy.Energy_C.value = obj->Energy.Energy_C.value + utempC/obj->Energy_K;
    obj->Energy.Energy.value = obj->Energy.Energy.value + utemp*4/obj->Energy_K;
    xSemaphoreGive(obj->Energy_lock);
#endif

#else   /* CF不清零 */
#if BL6552_ENERGY_USE_FLOAT /* 能量使用浮点运算 */
    xSemaphoreTake(obj->Energy_lock, portMAX_DELAY);
    obj->Energy.Energy_A.value = obj->EnergyMid.EnergyMid_A + (float)utempA/obj->Energy_K;
    obj->Energy.Energy_B.value = obj->EnergyMid.EnergyMid_B + (float)utempB/obj->Energy_K;
    obj->Energy.Energy_C.value = obj->EnergyMid.EnergyMid_C + (float)utempC/obj->Energy_K;
    obj->Energy.Energy.value = obj->EnergyMid.EnergyMid + (float)utemp*4/obj->Energy_K;
    xSemaphoreGive(obj->Energy_lock);
#else
    xSemaphoreTake(obj->Energy_lock, portMAX_DELAY);
    obj->Energy.Energy_A.value = obj->EnergyMid.EnergyMid_A + utempA*1000/obj->Energy_K;
    obj->Energy.Energy_B.value = obj->EnergyMid.EnergyMid_B + utempB*1000/obj->Energy_K;
    obj->Energy.Energy_C.value = obj->EnergyMid.EnergyMid_C + utempC*1000/obj->Energy_K;
    obj->Energy.Energy.value = obj->EnergyMid.EnergyMid + utemp*4000/obj->Energy_K;
    xSemaphoreGive(obj->Energy_lock);
#endif

    if ((utempA > 0x7FFFFF) || (utempB > 0x7FFFFF) || (utempC > 0x7FFFFF) || (utemp > 0x7FFFFF)) /* 超限清零 */
    {
        obj->EnergyMid.EnergyMid_A = obj->Energy.Energy_A.value;
        obj->EnergyMid.EnergyMid_B = obj->Energy.Energy_B.value;
        obj->EnergyMid.EnergyMid_C = obj->Energy.Energy_C.value;
        obj->EnergyMid.EnergyMid = obj->Energy.Energy.value;

        Bl6552_WriteReg( obj, Addr_USR_WRPROT, 0x005555, false );
        Bl6552_WriteReg( obj, Addr_SOFT_RESET, 0x5A5A5A, false );
        Bl6552_Config( obj );
    }
#endif
}

static int8_t Bl6552_Config(Bl6552_t *obj)
{
    /* 开用户写保护 */
    if( BSP_SUCCESS != Bl6552_WriteReg( obj, Addr_USR_WRPROT, 0x005555, true ) )
    {
        log_e( "Bl6552_WriteReg Addr_USR_WRPROT fail\r\n" );
        return BSP_ERROR;
    }

    /* 初始化通道增益寄存器 */
    // Bl6552_WriteReg( obj, Addr_GAIN1, 0x000000, false );    /* 各通道电流 1 倍增益 */
    // Bl6552_WriteReg( obj, Addr_GAIN2, 0x000000, false );    /* 各通道电压 1 倍增益*/

    /* 初始化各相校准寄存器 */

    /* 模式寄存器设置 */
    /* 快速有效值高通 */
    Bl6552_WriteReg( obj, Addr_MODE1, 0x400000, false );
    /* 有效值波形高通，有效值存器更新速度500ms，交流电频率50Hz */
    // Bl6552_WriteReg( obj, Addr_MODE2, 0x000000, false );
    /* 关闭CF输出，能量绝对值累加方式，全波无功/有功 */
    if( BSP_SUCCESS != Bl6552_WriteReg( obj, Addr_MODE3, 0x010000, true ) )
        return BSP_ERROR;

    /* 防潜动 有/无功功率2W，有效值5mA */
    Bl6552_WriteReg( obj, Addr_VAR_WA_CREEP, (((uint32_t)obj->WATT_K)<<12) + ((uint32_t)obj->WATT_K), false );  /* WA_CREEP=Watt/2 */
    // Bl6552_WriteReg( obj, Addr_REVP_RMS_CREEP, (uint32_t)obj->I_RMS_K/100, false ); /* RMS_CREEP = X_RMS 防潜采集时过滤 */

    /* CF 缩放比例设置 32 */
    if( BSP_SUCCESS != Bl6552_WriteReg( obj, Addr_CFDIV, 0x020, true ) )   /* CFDIV = 32 */
        return BSP_ERROR;

    /* 跌落电压阈值设置 100V */
    Bl6552_WriteReg( obj, Addr_SAGLVL_LINECYC, (obj->V_RMS_K*100)&0xFFF000 + 9, false );

    /* 电能脉冲读后清零设置，Reg3B~2F设置为读后清零 */
#if BL6552_CF_CLR_SEL
    Bl6552_WriteReg( obj, Addr_RST_ENG, 0xFFFFFF, false );
#else
    Bl6552_WriteReg( obj, Addr_RST_ENG, 0x000000, false );
#endif

    if( BSP_SUCCESS != Bl6552_WriteReg( obj, Addr_ADC_PD, 0x0C3, true ) )  /* 全使用 */
        return BSP_ERROR;

    /* 关闭写保护 */
    Bl6552_WriteReg( obj, Addr_USR_WRPROT, 0x000000, false );

    return BSP_SUCCESS;
}

/**
 * @brief Bl6552初始化
 * @param[in]  obj      Bl6552对象
 * @param[in]  uartId   串口外设编号
 * @param[in]  tx       串口TX引脚
 * @param[in]  rx       串口RX引脚
 * @return int8_t 
 * - @b Sucess : BSP_SUCCESS \n
 * - @b Fail
 * - @ref BSP_ERROR_INVALID_PARAM - 非法入参
 * - @ref BSP_ERROR_ALREADY_INIT - 已初始化
 * - @ref BSP_ERROR - 初始化出错
 * - @ref BSP_ERROR_NO_MEM - 内存出错
 */
int8_t Bl6552_Init( Bl6552_t *obj, UartId_t uartId, PinNames tx, PinNames rx )
{
    if (obj == NULL)
        return BSP_ERROR_INVALID_PARAM;

    if( obj->IsInitialized )
    {
        log_e( "Bl6552_Init error: has already Initialized\r\n" );
        return BSP_ERROR_ALREADY_INIT;
    }

    obj->UartId = uartId;
    if(BSP_SUCCESS != UartInit( uartId, tx, rx, 64 ))
        return BSP_ERROR;
    UartConfig( uartId, RX_TX, 4800, UART_8_BIT, UART_1_STOP_BIT, NO_PARITY, NO_FLOW_CTRL );

    /* 电参数计算系数设置 */
#if BL6552_ELECT_USE_FLOAT
    obj->I_RMS_K = 598290.157;      /* 206000*5.1/1.0975/16 = 59829.157  */
    // obj->V_RMS_K = 7989.814;        /* 13162/1.501/1.0975 = 7989.814 */
    obj->V_RMS_K = 7989.814;        /* 13162/1.0975 = 11992.7107 互感器版 */
    obj->WATT_K = 113.998;          /* 646.6*5.1/1.501/(1.0975*1.0975*16) = 113.998 */
#else
    obj->I_RMS_K = 59829;
    // obj->V_RMS_K = 7990;
    obj->V_RMS_K = 11993;        /* 互感器版 */
    obj->WATT_K = 114;
#endif

#if (BL6552_ENERGY_USE_FLOAT)
    obj->Energy_K = 186.62457;      /* 32*3600000*Power_K/(4194304*0.032768*16) = 186.62457 */
#else
    obj->Energy_K = 186;
#endif


    /* 电量统计清零 */
    memset( &obj->Energy, 0, sizeof(Bl6552_Energy_t) );
#if (!(BL6552_ENERGY_USE_FLOAT && BL6552_CF_CLR_SEL))
    memset( &obj->EnergyMid, 0, sizeof(Bl6552_EnergyMid_t) );
#endif

    /* RS485通信锁 */
    obj->WR_lock = xSemaphoreCreateBinary();    /* 初始时信号值为0 */
    if(obj->WR_lock == NULL)
    {
        log_e("bl6552 WR_lock create error\r\n");
        return BSP_ERROR_NO_MEM;
    }
    xSemaphoreGive(obj->WR_lock);

    /* 开用户写保护 */
    if( BSP_SUCCESS != Bl6552_WriteReg( obj, Addr_USR_WRPROT, 0x005555, true ) )
    {
        log_e( "Bl6552_WriteReg Addr_USR_WRPROT fail\r\n" );
        return BSP_ERROR;
    }
    vTaskDelay(1);

    /* 复位电参数寄存器、复位校表寄存器 */
    Bl6552_WriteReg( obj, Addr_SOFT_RESET, 0x5A5A5A, false );
    Bl6552_WriteReg( obj, Addr_SOFT_RESET, 0x55AA55, false );

    if( BSP_SUCCESS != Bl6552_Config(obj) )
    {
        log_e("Bl6552_Config error\r\n");
        return BSP_ERROR;
    }

    /* 电量统计读写锁 */
    obj->Energy_lock = xSemaphoreCreateBinary();
    if(obj->Energy_lock == NULL)
    {
        log_e("bl6552 Energy_lock create error\r\n");
        return BSP_ERROR_NO_MEM;
    }
    xSemaphoreGive(obj->Energy_lock);

    /* 电量统计定时器 */
    obj->bl_timer = xTimerCreate("bl6552", BL6552_ENERGY_PERIOD * portTICK_RATE_MS, pdTRUE, obj, blTimer_timeout_ind);
    if(obj->bl_timer == NULL)
    {
        log_e("bl6552 bl_timer create error\r\n");
        return BSP_ERROR_NO_MEM;
    }
    xTimerStart( obj->bl_timer, 0 );

    obj->IsInitialized = true;

    return BSP_SUCCESS;
}

/**
 * @brief Bl6552去初始化
 * @param  obj         Bl6552对象
 */
void Bl6552_DeInit( Bl6552_t *obj )
{
    if (obj == NULL)
        return;

    obj->IsInitialized = false;
    UartDeInit( obj->UartId );

    if (obj->WR_lock)
        vSemaphoreDelete( obj->WR_lock );
    if (obj->Energy_lock)
        vSemaphoreDelete( obj->Energy_lock );
    if (obj->bl_timer)
        xTimerDelete( obj->bl_timer, 0 );
}

/**
 * @brief Bl6552设置电量值
 * @param[in]  obj      Bl6552对象
 * @param[in]  Energy   设置的电量信息结构体
 * @return int8_t 
 * - @b Sucess : BSP_SUCCESS \n
 * - @b Fail
 * - @ref BSP_ERROR_INVALID_PARAM - 非法入参
 * - @ref BSP_ERROR_NO_INIT - 未初始化
 */
int8_t Bl6552_SetEnergy( Bl6552_t *obj, Bl6552_Energy_t *Energy )
{
    if ((obj == NULL) || (Energy == NULL))
        return BSP_ERROR_INVALID_PARAM;
    
    if ( !obj->IsInitialized )
        return BSP_ERROR_NO_INIT;

    xSemaphoreTake(obj->Energy_lock, portMAX_DELAY);
    memcpy( &obj->Energy, Energy, sizeof(Bl6552_Energy_t) );
#if (!(BL6552_ENERGY_USE_FLOAT && BL6552_CF_CLR_SEL))
    memset( &obj->EnergyMid, 0, sizeof(Bl6552_EnergyMid_t) );
#endif
    xSemaphoreGive(obj->Energy_lock);

#if !BL6552_CF_CLR_SEL
    Bl6552_WriteReg( obj, Addr_USR_WRPROT, 0x005555, false );
    Bl6552_WriteReg( obj, Addr_SOFT_RESET, 0x5A5A5A, false );
    Bl6552_Config( obj );
#endif

    return BSP_SUCCESS;
}

/**
 * @brief Bl6552获取电量值
 * @param[in]  obj      Bl6552对象
 * @param[in]  Energy   统计的电量信息结构体
 * @return int8_t 
 * - @b Sucess : BSP_SUCCESS \n
 * - @b Fail
 * - @ref BSP_ERROR_INVALID_PARAM - 非法入参
 * - @ref BSP_ERROR_NO_INIT - 未初始化
 */
int8_t Bl6552_GetEnergy( Bl6552_t *obj, Bl6552_Energy_t *Energy )
{
    if ((obj == NULL) || (Energy == NULL))
        return BSP_ERROR_INVALID_PARAM;

    if( !obj->IsInitialized )
        return BSP_ERROR_NO_INIT;

    xSemaphoreTake(obj->Energy_lock, portMAX_DELAY);
    memcpy( Energy, &obj->Energy, sizeof(Bl6552_Energy_t) );
    xSemaphoreGive(obj->Energy_lock);

    return BSP_SUCCESS;
}

/**
 * @brief 获取电量瞬时参数
 * @param[in]  obj      Bl6552对象
 * @param[in]  Elect    电参数信息
 * @param[in]  mask     电参数选项掩码
 * @return int8_t 
 * - @b Sucess :  \n
 * - @b Fail
 * - @ref BSP_ERROR_INVALID_PARAM - 非法入参
 * - @ref BSP_ERROR_NO_INIT - 未初始化
 * - 其他寄存器读取错误
 * @par 示例:
 * @code
 *    Bl6552_GetElect( obj, Elect, BL6552_ELECT_PERIOD | BL6552_ELECT_V_RMS );
 *    Bl6552_GetElect( obj, Elect, BL6552_ELECT_ALL );
 * @endcode
 */
int8_t Bl6552_GetElect( Bl6552_t *obj, Bl6552_Elect_t *Elect, uint32_t mask )
{
    uint32_t utemp;
    int32_t itemp;
    int8_t ret;

    if ((obj == NULL) || (Elect == NULL) || (mask == 0))
        return BSP_ERROR_INVALID_PARAM;

    if (!obj->IsInitialized)
    {
        log_e( "Bl6552 no Initialized\r\n" );
        return BSP_ERROR_NO_INIT;
    }

    if (mask & BL6552_ELECT_V_RMS)  /* 读电压有效值 unit: 0.1伏 */
    {
        ret = Bl6552_ReadRegUint( obj, Addr_VA_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VA_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VA_RMS.value = (float)utemp/obj->V_RMS_K;
        log_v("VA_RMS = %.3f\r\n", Elect->VA_RMS);
#else
        Elect->VA_RMS.value = utemp*10/obj->V_RMS_K;
        log_v("VA_RMS = %d\r\n", Elect->VA_RMS);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_VB_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VB_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VB_RMS.value = (float)utemp/obj->V_RMS_K;
        log_v("VB_RMS = %.3f\r\n", Elect->VB_RMS);
#else
        Elect->VB_RMS.value = utemp*10/obj->V_RMS_K;
        log_v("VB_RMS = %d\r\n", Elect->VB_RMS);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_VC_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VC_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VC_RMS.value = (float)utemp/obj->V_RMS_K;
        log_v("VC_RMS = %.3f\r\n", Elect->VC_RMS);
#else
        Elect->VC_RMS.value = utemp*10/obj->V_RMS_K;
        log_v("VC_RMS = %d\r\n", Elect->VC_RMS);
#endif
    }

    if (mask & BL6552_ELECT_PERIOD) /* 读工频 unit: 0.01Hz */
    {
        ret = Bl6552_ReadRegUint( obj, Addr_PERIOD, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_PERIOD = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->PERIOD.value = (float)10000000/(float)utemp;
        log_v("PERIOD = %.3f\r\n", Elect->PERIOD);
#else
        Elect->PERIOD.value = 10000000*10/utemp;
        log_v("PERIOD = %d\r\n", Elect->PERIOD);
#endif
    }

    if (mask & BL6552_ELECT_I_RMS)  /* 读电流有效值 unit: 0.001安 */
    {
        ret = Bl6552_ReadRegUint( obj, Addr_IA_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_IA_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->IA_RMS.value = (float)utemp/obj->I_RMS_K;
        log_v("IA_RMS = %.3f\r\n", Elect->IA_RMS);
#else
        Elect->IA_RMS.value = utemp*1000/obj->I_RMS_K;
        log_v("IA_RMS = %d\r\n", Elect->IA_RMS);
#endif
#if (BL6552_RMS_CREEP_VALUE > 0)
        #if BL6552_ELECT_USE_FLOAT
        Elect->IA_RMS.value = (Elect->IA_RMS.value < (float)BL6552_RMS_CREEP_VALUE/1000) ? 0 : Elect->IA_RMS.value;
        #else
        Elect->IA_RMS.value = (Elect->IA_RMS.value < BL6552_RMS_CREEP_VALUE) ? 0 : Elect->IA_RMS.value;
        #endif
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_IB_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_IB_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->IB_RMS.value = (float)utemp/obj->I_RMS_K;
        log_v("IB_RMS = %.3f\r\n", Elect->IB_RMS);
#else
        Elect->IB_RMS.value = utemp*1000/obj->I_RMS_K;
        log_v("IB_RMS = %d\r\n", Elect->IB_RMS);
#endif
#if (BL6552_RMS_CREEP_VALUE > 0)
        #if BL6552_ELECT_USE_FLOAT
        Elect->IB_RMS.value = (Elect->IB_RMS.value < (float)BL6552_RMS_CREEP_VALUE/1000) ? 0 : Elect->IB_RMS.value;
        #else
        Elect->IB_RMS.value = (Elect->IB_RMS.value < BL6552_RMS_CREEP_VALUE) ? 0 : Elect->IB_RMS.value;
        #endif
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_IC_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_IC_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->IC_RMS.value = (float)utemp/obj->I_RMS_K;
        log_v("IC_RMS = %.3f\r\n", Elect->IC_RMS);
#else
        Elect->IC_RMS.value = utemp*1000/obj->I_RMS_K;
        log_v("IC_RMS = %d\r\n", Elect->IC_RMS);
#endif
#if (BL6552_RMS_CREEP_VALUE > 0)
        #if BL6552_ELECT_USE_FLOAT
        Elect->IC_RMS.value = (Elect->IC_RMS.value < (float)BL6552_RMS_CREEP_VALUE/1000) ? 0 : Elect->IC_RMS.value;
        #else
        Elect->IC_RMS.value = (Elect->IC_RMS.value < BL6552_RMS_CREEP_VALUE) ? 0 : Elect->IC_RMS.value;
        #endif
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_IN_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_IN_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->IN_RMS.value = (float)utemp/obj->I_RMS_K;
        log_v("IN_RMS = %.3f\r\n", Elect->IN_RMS);
#else
        Elect->IN_RMS.value = utemp*1000/obj->I_RMS_K;
        log_v("IN_RMS = %d\r\n", Elect->IN_RMS);
#endif
#if (BL6552_RMS_CREEP_VALUE > 0)
        #if BL6552_ELECT_USE_FLOAT
        Elect->IN_RMS.value = (Elect->IN_RMS.value < (float)BL6552_RMS_CREEP_VALUE/1000) ? 0 : Elect->IN_RMS.value;
        #else
        Elect->IN_RMS.value = (Elect->IN_RMS.value < BL6552_RMS_CREEP_VALUE) ? 0 : Elect->IN_RMS.value;
        #endif
#endif
    }

#if BL6552_USE_FAST_RMS
    if (mask & BL6552_ELECT_I_FAST_RMS) /* 读电流快速有效值 unit: 0.001安 */
    {
        ret = Bl6552_ReadRegUint( obj, Addr_IA_FAST_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_IA_FAST_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->IA_FAST_RMS.value = (float)utemp/obj->Current_K;
        log_v("IA_FAST_RMS = %.3f\r\n", Elect->IA_FAST_RMS);
#else
        Elect->IA_FAST_RMS.value = utemp*100/obj->Current_K;
        log_v("IA_FAST_RMS = %d\r\n", Elect->IA_FAST_RMS);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_IB_FAST_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_IB_FAST_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->IB_FAST_RMS.value = (float)utemp/obj->Current_K;
        log_v("IB_FAST_RMS = %.3f\r\n", Elect->IB_FAST_RMS);
#else
        Elect->IB_FAST_RMS.value = utemp*100/obj->Current_K;
        log_v("IB_FAST_RMS = %d\r\n", Elect->IB_FAST_RMS);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_IC_FAST_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_IC_FAST_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->IC_FAST_RMS.value = (float)utemp/obj->Current_K;
        log_v("IC_FAST_RMS = %.3f\r\n", Elect->IC_FAST_RMS);
#else
        Elect->IC_FAST_RMS.value = utemp*100/obj->Current_K;
        log_v("IC_FAST_RMS = %d\r\n", Elect->IC_FAST_RMS);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_IN_FAST_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_IN_FAST_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->IN_FAST_RMS.value = (float)utemp/obj->Current_K;
        log_v("IN_FAST_RMS = %.3f\r\n", Elect->IN_FAST_RMS);
#else
        Elect->IN_FAST_RMS.value = utemp*100/obj->Current_K;
        log_v("IN_FAST_RMS = %d\r\n", Elect->IN_FAST_RMS);
#endif
    }

    if (mask & BL6552_ELECT_V_FAST_RMS) /* 读电压快速有效值 unit: 0.1伏 */
    {
        ret = Bl6552_ReadRegUint( obj, Addr_VA_FAST_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VA_FAST_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VA_FAST_RMS.value = (float)utemp/obj->Voltage_K;
        log_v("VA_FAST_RMS = %d\r\n", Elect->VA_FAST_RMS);
#else
        Elect->VA_FAST_RMS.value = utemp*10/obj->Voltage_K;
        log_v("VA_FAST_RMS = %d\r\n", Elect->VA_FAST_RMS);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_VB_FAST_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VB_FAST_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VB_FAST_RMS.value = (float)utemp/obj->Voltage_K;
        log_v("VB_FAST_RMS = %.3f\r\n", Elect->VB_FAST_RMS);
#else
        Elect->VB_FAST_RMS.value = utemp*10/obj->Voltage_K;
        log_v("VB_FAST_RMS = %d\r\n", Elect->VB_FAST_RMS);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_VC_FAST_RMS, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VC_FAST_RMS = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VC_FAST_RMS.value = (float)utemp/obj->Voltage_K;
        log_v("VC_FAST_RMS = %.3f\r\n", Elect->VC_FAST_RMS);
#else
        Elect->VC_FAST_RMS.value = utemp*10/obj->Voltage_K;
        log_v("VC_FAST_RMS = %d\r\n", Elect->VC_FAST_RMS);
#endif
    }
#endif

    if (mask & BL6552_ELECT_WATT)   /* 读有功功率 unit: 0.1瓦 */
    {
        ret = Bl6552_ReadRegInt( obj, Addr_WATT_A, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_WATT_A = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->WATT_A.value = (float)abs(itemp)/obj->WATT_K;
        log_v("WATT_A = %.3f\r\n", Elect->WATT_A);
#else
        Elect->WATT_A.value = abs(itemp)*10/obj->WATT_K;
        log_v("WATT_A = %d\r\n", Elect->WATT_A);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_WATT_B, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_WATT_B = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->WATT_B.value = (float)abs(itemp)/obj->WATT_K;
        log_v("WATT_B = %.3f\r\n", Elect->WATT_B);
#else
        Elect->WATT_B.value = abs(itemp)*10/obj->WATT_K;
        log_v("WATT_B = %d\r\n", Elect->WATT_B);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_WATT_C, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_WATT_C = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->WATT_C.value = (float)abs(itemp)/obj->WATT_K;
        log_v("WATT_C = %.3f\r\n", Elect->WATT_C);
#else
        Elect->WATT_C.value = abs(itemp)*10/obj->WATT_K;
        log_v("WATT_C = %d\r\n", Elect->WATT_C);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_WATT, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_WATT = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->WATT.value = (float)abs(itemp)*4/obj->WATT_K;
        log_v("WATT = %.3f\r\n", Elect->WATT);
#else
        Elect->WATT.value = abs(itemp)*40/obj->WATT_K;
        log_v("WATT = %d\r\n", Elect->WATT);
#endif
    }

#if BL6552_USE_VAR
    if (mask & BL6552_ELECT_VAR)    /* 读无功功率 unit: 0.1瓦 */
    {
        ret = Bl6552_ReadRegInt( obj, Addr_VAR_A, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VAR_A = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VAR_A.value = (float)abs(itemp)/obj->WATT_K;
        log_v("VAR_A = %.3f\r\n", Elect->VAR_A);
#else
        Elect->VAR_A.value = abs(itemp)*10/obj->WATT_K;
        log_v("VAR_A = %d\r\n", Elect->VAR_A);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_VAR_B, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VAR_B = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VAR_B.value = (float)abs(itemp)/obj->WATT_K;
        log_v("VAR_B = %.3f\r\n", Elect->VAR_B);
#else
        Elect->VAR_B.value = abs(itemp)*10/obj->WATT_K;
        log_v("VAR_B = %d\r\n", Elect->VAR_B);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_VAR_C, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VAR_C = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VAR_C.value = (float)abs(itemp)/obj->WATT_K;
        log_v("VAR_C = %.3f\r\n", Elect->VAR_C);
#else
        Elect->VAR_C.value = abs(itemp)*10/obj->WATT_K;
        log_v("VAR_C = %d\r\n", Elect->VAR_C);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_VAR, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VAR = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VAR.value = (float)abs(itemp)*4/obj->WATT_K;
        log_v("VAR = %.3f\r\n", Elect->VAR);
#else
        Elect->VAR.value = abs(itemp)*40/obj->WATT_K;
        log_v("VAR = %d\r\n", Elect->VAR);
#endif
    }
#endif

#if BL6552_USE_VA
    if (mask & BL6552_ELECT_VA)     /* 读视在功率 unit: 0.1瓦 */
    {
        ret = Bl6552_ReadRegInt( obj, Addr_VA_A, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VA_A = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VA_A.value = (float)abs(itemp)/obj->WATT_K;
        log_v("VA_A = %.3f\r\n", Elect->VA_A);
#else
        Elect->VA_A.value = abs(itemp)*10/obj->WATT_K;
        log_v("VA_A = %d\r\n", Elect->VA_A);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_VA_B, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VA_B = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VA_B.value = (float)abs(itemp)/obj->WATT_K;
        log_v("VA_B = %.3f\r\n", Elect->VA_B);
#else
        Elect->VA_B.value = abs(itemp)*10/obj->WATT_K;
        log_v("VA_B = %d\r\n", Elect->VA_B);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_VA_C, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VA_C = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VA_C.value = (float)abs(itemp)/obj->WATT_K;
        log_v("VA_C = %.3f\r\n", Elect->VA_C);
#else
        Elect->VA_C.value = abs(itemp)*10/obj->WATT_K;
        log_v("VA_C = %d\r\n", Elect->VA_C);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_VA, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_VA = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->VA.value = (float)abs(itemp)*4/obj->WATT_K;
        log_v("VA = %.3f\r\n", Elect->VA);
#else
        Elect->VA.value = abs(itemp)*40/obj->WATT_K;
        log_v("VA = %d\r\n", Elect->VA);
#endif
    }
#endif

#if BL6552_USE_ANGLE
    if (mask & BL6552_ELECT_ANGLE)  /* 读相波形夹角 unit: 0.1° */
    {
        ret = Bl6552_ReadRegUint( obj, Addr_ANGLE_AB, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_ANGLE_AB = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->ANGLE_AB.value = (float)(36*utemp)/1000;
        log_v("ANGLE_AB = %.3f\r\n", Elect->ANGLE_AB);
#else
        Elect->ANGLE_AB.value = (36*utemp)/100;
        log_v("ANGLE_AB = %d\r\n", Elect->ANGLE_AB);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_ANGLE_BC, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_ANGLE_BC = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->ANGLE_BC.value = (float)(36*utemp)/1000;
        log_v("ANGLE_BC = %.3f\r\n", Elect->ANGLE_BC);
#else
        Elect->ANGLE_BC.value = (36*utemp)/100;
        log_v("ANGLE_BC = %d\r\n", Elect->ANGLE_BC);
#endif

        ret = Bl6552_ReadRegUint( obj, Addr_ANGLE_AC, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_ANGLE_AC = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->ANGLE_AC.value = (float)(36*utemp)/1000;
        log_v("ANGLE_AC = %.3f\r\n", Elect->ANGLE_AC);
#else
        Elect->ANGLE_AC.value = (36*utemp)/100;
        log_v("ANGLE_AC = %d\r\n", Elect->ANGLE_AC);
#endif
    }
#endif

#if BL6552_USE_PF
    if (mask & BL6552_ELECT_PF)     /* 读功率因子 unit: 0.01 */
    {
        ret = Bl6552_ReadRegInt( obj, Addr_PF_A, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_PF_A = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->PF_A.value = (float)abs(itemp)/(0x800000);
        log_v("PF_A = %.3f\r\n", Elect->PF_A);
#else
        Elect->PF_A.value = abs(itemp)*100/(0x800000);
        log_v("PF_A = %d\r\n", Elect->PF_A);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_PF_B, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_PF_B = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->PF_B.value = (float)abs(itemp)/(0x800000);
        log_v("PF_B = %.3f\r\n", Elect->PF_B);
#else
        Elect->PF_B.value = abs(itemp)*100/(0x800000);
        log_v("PF_B = %d\r\n", Elect->PF_B);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_PF_C, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_PF_C = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->PF_C.value = (float)abs(itemp)/(0x800000);
        log_v("PF_C = %.3f\r\n", Elect->PF_C);
#else
        Elect->PF_C.value = abs(itemp)*100/(0x800000);
        log_v("PF_C = %d\r\n", Elect->PF_C);
#endif

        ret = Bl6552_ReadRegInt( obj, Addr_PF, &itemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_PF = %d\r\n", itemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->PF.value = (float)abs(itemp)/(0x800000);
        log_v("PF = %.3f\r\n", Elect->PF);
#else
        Elect->PF.value = abs(itemp)*100/(0x800000);
        log_v("PF = %d\r\n", Elect->PF);
#endif
    }
#endif

#if BL6552_USE_TPS
    if (mask & BL6552_ELECT_TPS)    /* 读内部温度值 unit: 0.1摄氏度 */
    {
        ret = Bl6552_ReadRegUint( obj, Addr_TPS1, &utemp );
        if (ret != BSP_SUCCESS)
            goto error_handle;
        log_v("Addr_TPS1 = %d\r\n", utemp);
#if BL6552_ELECT_USE_FLOAT
        Elect->TPS1.value = (float)((float)(utemp-64)*125/590 - 40);
        log_v("TPS1 = %.3f\r\n", Elect->TPS1);
#else
        Elect->TPS1.value = (int16_t)((utemp-64)*125/590 - 40);
        log_v("TPS1 = %d\r\n", Elect->TPS1);
#endif
    }
#endif


    return BSP_SUCCESS;

error_handle:
    log_e( "Bl6552_ReadReg error(%d)\r\n", ret );
    return ret;
}


#endif  /* DRV_BL6552_EN */

/*********** (C) COPYRIGHT 2021 FiberHome *****END OF FILE****/
